package com.kashow.base.rx;

import com.kashow.base.exception.HttpRequestException;
import com.kashow.base.exception.NoAuthException;
import com.kashow.bean.BaseBean;
import com.kashow.bean.BaseHttpResult;
import com.kashow.bean.Data;
import com.kashow.bean.HttpResult;

import java.util.List;

import rx.Observable;
import rx.Subscriber;
import rx.functions.Func1;

public class
RxUtil {

    /**
     * 统一返回结果处理
     * @param <T>
     * @return
     */
    public static <T extends BaseBean> Observable.Transformer<HttpResult<? extends Data<T>>, List<T>> handleListResult() {   //compose判断结果
        return new Observable.Transformer<HttpResult<? extends Data<T>>, List<T>>() {
            @Override
            public Observable<List<T>> call(Observable<HttpResult<? extends Data<T>>> httpResponse) {
                return httpResponse.map(new Func1<HttpResult<? extends Data<T>>, List<T>>() {
                    @Override
                    public List<T> call(HttpResult<? extends Data<T>> httpResult) {
                        if (httpResult == null) {
                            throw new HttpRequestException();
                        }
                        if (!httpResult.isSuccess()) {
                            throw new HttpRequestException(httpResult.getMsg());
                        }
                        return httpResult.getData().getResult();
                    }
                });
            }
        };
    }

    /**
     * 统一返回结果处理
     * @param <T>
     * @return
     */
    public static <T> Observable.Transformer<HttpResult<T>, T> handleResult() {   //compose判断结果
        return new Observable.Transformer<HttpResult<T>, T>() {
            @Override
            public Observable<T> call(Observable<HttpResult<T>> httpResponse) {
                return httpResponse.map(new Func1<HttpResult<T>, T>() {
                    @Override
                    public T call(HttpResult<T> httpResult) {
                        if (httpResult == null) {
                            throw new HttpRequestException();
                        }
                        if (!httpResult.isSuccess()) {
                            String msg = httpResult.getMsg();
                            if ("请登录".equals(msg)) {
                                throw new NoAuthException(msg);
                            }
                            throw new HttpRequestException(msg);
                        }
                        return httpResult.getData();
                    }
                });
            }
        };
    }


    /**
     * 统一返回结果处理
     * @param <T>
     * @return
     */
    public static <T> Observable.Transformer<HttpResult<T>, T> FlatMaphandleResult() {   //compose判断结果
        return new Observable.Transformer<HttpResult<T>, T>() {
            @Override
            public Observable<T> call(Observable<HttpResult<T>> httpResponse) {
                return httpResponse.flatMap(new Func1<HttpResult<T>, Observable<T>>() {
                    @Override
                    public Observable<T> call(HttpResult<T> httpResult) {
                        if (httpResult == null) {
                            Observable.error(new HttpRequestException());
                        }
                        if (!httpResult.isSuccess()) {
                            String msg = httpResult.getMsg();
                            if ("请登录".equals(msg)) {
                                Observable.error(new NoAuthException(msg));
                            }
                            Observable.error(new HttpRequestException(msg));
                        }
                        return createData(httpResult.getData());
                    }
                });
            }
        };
    }

    public static <T extends BaseHttpResult> Observable.Transformer<T, Boolean> getHttpResultSuccess() {
        return new Observable.Transformer<T, Boolean>() {
            @Override
            public Observable<Boolean> call(Observable<T> observable) {
                return observable.map(new Func1<T, Boolean>() {
                    @Override
                    public Boolean call(T t) {
                        if (t == null) {
                            throw new HttpRequestException();
                        }
                        if (!t.isSuccess()) {
                            String msg = t.getMsg();
                            if ("请登录".equals(msg)) {
                                throw new NoAuthException(msg);
                            }
                            throw new HttpRequestException(msg);
                        }
                        return true;
                    }
                });
            }
        };
    }


    public static <T extends BaseHttpResult> Observable.Transformer<T, T> getHttpResult() {
        return new Observable.Transformer<T, T>() {
            @Override
            public Observable<T> call(Observable<T> observable) {
                return observable.map(new Func1<T, T>() {
                    @Override
                    public T call(T t) {
                        if (t == null) {
                            throw new HttpRequestException();
                        }
                        if (!t.isSuccess()) {
                            String msg = t.getMsg();
                            if ("请登录".equals(msg)) {
                                throw new NoAuthException(msg);
                            }
                            throw new HttpRequestException(msg);
                        }
                        return t;
                    }
                });
            }
        };
    }

    /**
     * 生成Observable
     * @param <T>
     * @return
     */
    public static <T> Observable<T> createData(final T t) {
        return Observable.create(new Observable.OnSubscribe<T>() {
            @Override
            public void call(Subscriber<? super T> subscriber) {
                try {
                    subscriber.onNext(t);
                    subscriber.onCompleted();
                } catch (Exception e) {
                    subscriber.onError(e);
                }
            }
        });
    }
}
